<script setup lang="ts">
// 搜索表单绑定对象
import { nextTick, onMounted, reactive, ref, Ref } from "vue";
import SysDialog from "@/components/dialog/SysDialog.vue";
import useDialog from "@/hooks/useDialog.ts";
// 弹框属性
const { dialog, onShow, onClose, onConfirm } = useDialog();
import useInstance from "@/hooks/useInstance.ts";
// 获取全局 global
const { global } = useInstance();
import { getListApi, deleteApi, getLogDetail, getLogTitle } from "@/api/log/index.ts";
import { SysOperLogClean, LogListParam, SysOperLog } from "@/api/log/type.ts";
import {ElMessage} from "element-plus";

// 总条数
const total: Ref<number> = ref(0);

// 搜索表单
const searchParam = reactive<LogListParam>({
  title: '',
  state: undefined,
  page: 1,
  limit: 11,
});

// 表格高度
const tableHeight = ref()

// 日志表格列表
const logList = ref<SysOperLog[]>([]);


// 日志标题
const logTitles = ref<string[]>([]);

// 日志详情数据--form表单数据
let logDetail = reactive<SysOperLog>({
  id: undefined,
  oper: '',
  title: '',
  businessType: undefined,
  uri: '',
  requestMethod: '',
  status: undefined,
  optParam: '',
  errorMsg: '',
  operTime: '',
  ip: '',
  executionTime: undefined,
  operLocation: '',
});

// 删除日志的表单数据
const deleteLogForm = reactive<SysOperLogClean>({
  title: '',
  days: '15',
});

// 获取日志列表
const getSystemLog = async () => {
  const result = await getListApi(searchParam);
  if (result.code === 200) {
    logList.value = result.data.list;
    total.value = result.data.total;
  }
};

// 获取日志标题
const getLogTitles = async () => {
  const result = await getLogTitle();
  if (result.code === 200) {
    logTitles.value = result.data;
  }
};

// 搜索日志
const searchLog = () => {
  getSystemLog();
};

// 重置搜索表单
const resetForm = () => {
  searchParam.title = '';
  searchParam.state = undefined;
  getSystemLog();
};

// 在 script setup 中添加
// 弹框状态
const dialogConfig = reactive({
  detail: {
    visible: false,
    title: '日志详情',
    width: 950,
    height: 450
  },
  clean: {
    visible: false,
    title: '清空日志',
    width: 520,
    height: 200
  }
});

// 打开弹框
const openDialog = (type: 'detail' | 'clean') => {
  dialogConfig[type].visible = true;
};

// 关闭弹框
const closeDialog = (type: 'detail' | 'clean') => {
  dialogConfig[type].visible = false;
};


// 获取日志详情
const fetchLogDetail = async (id: number) => {
  const result = await getLogDetail(id);
  if (result.code === 200) {
    Object.assign(logDetail, result.data);
    openDialog('detail');
  }
};

// 删除日志
const deleteLog = async () => {
  try {
    const result = await deleteApi(deleteLogForm);
    closeDialog('clean');
    ElMessage.success('日志清理成功');
    getSystemLog();
  } catch {
    closeDialog('clean');
    ElMessage.info('已取消清理');
  }
};

// 页面加载完毕获取日志列表
onMounted(() => {
  nextTick(() => {
    tableHeight.value = window.innerHeight - 280
  })
  getSystemLog();
});
</script>

<template>
  <el-main>
    <el-card style="height: 70px; margin-bottom: 10px">
      <el-form inline :model="searchParam">
        <el-form-item label="模块标题">
          <el-select v-model="searchParam.title" placeholder="请选择日志标题" @focus="getLogTitles">
            <el-option v-for="title in logTitles" :key="title" :label="title" :value="title" />
          </el-select>
        </el-form-item>

        <el-form-item label="执行状态">
          <el-select style="width: 110px" v-model="searchParam.state">
            <el-option label="成功" value="0"></el-option>
            <el-option label="失败" value="1"></el-option>
          </el-select>
        </el-form-item>
        <el-form-item>
          <el-button type='primary' icon="search" @click="searchLog">搜索</el-button>
          <el-button icon="Refresh" @click="resetForm">重置</el-button>
        </el-form-item>
        <el-form-item>
          <!-- 清空日志按钮 -->
          <el-button type="danger" icon="Delete" @click="openDialog('clean')">清空日志</el-button>
        </el-form-item>
      </el-form>
    </el-card>


      <el-table  :height="tableHeight" :data="logList"  border>
        <el-table-column type="index" label="序号" width="55" />
        <el-table-column prop="title" label="操作模块" width="120" />
        <el-table-column prop="oper" label="操作人" width="120" />
        <el-table-column label="业务类型" width="90">
          <template #="{row}">
            <el-tag v-if="row.businessType == '0'" type="success">其它</el-tag>
            <el-tag v-else-if="row.businessType == '1'" type="info">新增</el-tag>
            <el-tag v-else-if="row.businessType == '2'" type="warning">修改</el-tag>
            <el-tag v-else-if="row.businessType == '3'" type="danger">删除</el-tag>
          </template>
        </el-table-column>

        <el-table-column prop="uri" label="uri" width="175" />
        <el-table-column label="状态" width="80">
          <template #="{row}">
            <el-tag v-if="row.status == '0'" type="primary">成功</el-tag>
            <el-tag v-else-if="row.status == '1'" type="danger">失败</el-tag>
          </template>
        </el-table-column>
        <el-table-column label="接口耗时" width="90">
          <template #="{row}">
            <el-tag type="danger">{{ row.executionTime }}ms</el-tag>
          </template>
        </el-table-column>
        <el-table-column prop="operTime" label="执行时间" width="170" />
        <el-table-column prop="ip" label="外网IP" width="140" />
        <el-table-column prop="operLocation" label="归属地" width="160" />
        <el-table-column label="操作">
          <template #="{row}">
            <el-button link type="primary" size="small" icon="View" @click="fetchLogDetail(row.id)">日志详情</el-button>
          </template>
        </el-table-column>
      </el-table>

    <!--分页器-->
    <div class="pagination">
      <el-pagination
          v-model:current-page="searchParam.page"
          v-model:page-size="searchParam.limit"
          :page-sizes="[10, 15, 20, 25]"
          :background="true"
          layout="prev, pager, next, jumper,->,sizes,total"
          :total="total"
          @current-change="getSystemLog"
          @size-change="getSystemLog"
      />
    </div>


    <SysDialog
        :title="dialogConfig.detail.title"
        :width="dialogConfig.detail.width"
        :height="dialogConfig.detail.height"
        :visible="dialogConfig.detail.visible"
        @on-close="() => closeDialog('detail')"
        @on-confirm="() => closeDialog('detail')">
      <template v-slot:content>
        <el-form :inline="true" :model="logDetail" class="demo-form-inline" label-width="auto">
          <el-form-item label="操作模块:">
            <el-input v-model="logDetail.title" />
          </el-form-item>
          <el-form-item label="操作人:">
            <el-input v-model="logDetail.oper" />
          </el-form-item>
          <el-form-item label="执行时间:">
            <el-input v-model="logDetail.operTime" />
          </el-form-item>
          <el-form-item label="业务类型:">
            <el-tag style="width:190px" v-if="logDetail.businessType == 0" effect="dark" type="success">其它</el-tag>
            <el-tag style="width:190px" v-else-if="logDetail.businessType == 1" effect="dark" type="primary">新增</el-tag>
            <el-tag style="width:190px" v-else-if="logDetail.businessType == 2" effect="dark" type="warning">修改</el-tag>
            <el-tag style="width:190px" v-else-if="logDetail.businessType == 3" effect="dark" type="danger">删除</el-tag>
          </el-form-item>
          <el-form-item label="ip地址:">
            <el-input v-model="logDetail.ip" />
          </el-form-item>
          <el-form-item label="归属地:">
            <el-input v-model="logDetail.operLocation" />
          </el-form-item>
          <el-form-item label="URI:">
            <el-tag type="danger" effect="dark">
              {{ logDetail.uri }}
            </el-tag>
          </el-form-item>
          <el-form-item label="请求方式:">
            <el-tag type="success" effect="dark">
              {{ logDetail.requestMethod }}
            </el-tag>
          </el-form-item>
          <el-form-item label="状态:">
            <el-tag type="primary" effect="dark">
              {{ logDetail.status === 0 ? '成功' : '失败' }}
            </el-tag>
          </el-form-item>
          <el-form-item label="接口耗时:">
            <el-tag type="warning" effect="dark">
              {{ logDetail.executionTime }}/ms
            </el-tag>
          </el-form-item>
          <el-row>
            <el-col :span="24">
              <!-- 请求参数 -->
              <el-form-item label="请求参数:">
                <el-input style="width: 800px" type="textarea" v-model="logDetail.optParam" rows="5" />
              </el-form-item>
            </el-col>
            <el-col :span="24">
              <!-- 异常情况 -->
              <el-form-item label="异常情况:">
                <el-input v-if="logDetail.errorMsg" style="width: 800px" type="textarea" v-model="logDetail.errorMsg" rows="5" />
                <div v-else>  <el-tag style="width:190px" type="primary">接口执行正常</el-tag></div>
              </el-form-item>
            </el-col>
          </el-row>
        </el-form>
      </template>
    </SysDialog>

    <!-- 清空日志弹框 -->
    <SysDialog
        :title="dialogConfig.clean.title"
        :width="dialogConfig.clean.width"
        :height="dialogConfig.clean.height"
        :visible="dialogConfig.clean.visible"
        @on-close="() => closeDialog('clean')"
        @on-confirm="deleteLog">
      <template v-slot:content>
        <el-form :model="deleteLogForm">
          <el-form-item label="模块标题">
            <el-select v-model="deleteLogForm.title" placeholder="请选择日志标题" @focus="getLogTitles" style="width: 220px">
              <el-option v-for="title in logTitles" :key="title" :label="title" :value="title" />
            </el-select>
          </el-form-item>
          <el-form-item label="清理时间">
            <el-radio-group v-model="deleteLogForm.days">
              <el-radio label="15">15天前</el-radio>
              <el-radio label="10">10天前</el-radio>
              <el-radio label="5">5天前</el-radio>
              <el-radio label="0">全部</el-radio>
            </el-radio-group>
          </el-form-item>
        </el-form>
      </template>
    </SysDialog>
  </el-main>
</template>

<style scoped lang="scss">
.el-select {
  --el-select-width: 150px;
}

.demo-form-inline .el-input {
  --el-input-width: 190px;
}

.demo-form-inline .el-select {
  --el-select-width: 190px;
}

.pagination {
  margin-top: 20px;
}
</style>
